﻿using System;
using System.IO;
using System.Linq;
using System.Text;
using System.Xml;
using System.Xml.Serialization;
using System.Xml.Linq;

namespace Smugmug
{
    [XmlRoot("rsp")]
    public class RestResponse : IResponse
    {
        [XmlAttribute("method")]
        public string Method { get; set; }

        [XmlAttribute("err")]
        public ResponseError Error { get; set; }

        [XmlIgnore]
        public string Body { get; set; }

        public RestResponse()
        {
        }

        public RestResponse(string xml)
        {
            Parse(xml, this);
        }

        protected static void Parse(string xml, RestResponse response)
        {
            using (TextReader tr = new StringReader(xml))
            {
                XDocument doc = XDocument.Load(tr);
                string status = (from c in doc.Root.Attributes()
                                 where c.Name == "stat"
                                 select c.Value).FirstOrDefault();
                if (status == "fail")
                {
                    var errorElement = (from c in doc.Root.Descendants("err")
                                        select c).FirstOrDefault();
                    response.Error = new ResponseError
                    {
                        ErrorCode = Int32.Parse(errorElement.FirstAttribute.Value),
                        Message = errorElement.FirstAttribute.NextAttribute.Value
                    };
                    return;
                }

                response.Method = (from c in doc.Root.Descendants("method")
                                   select c).FirstOrDefault().Value;
                //TODO: set the body text here
            }
        }
    }

    [XmlRoot("rsp")]
    public class RestResponse<T> : RestResponse, IResponse<T>
        where T : new()
    {        
        public T Data { get; set; }

        public RestResponse()
        {
        }

        public RestResponse(string xml)
        {
            Parse(xml, this);
        }

        protected static void Parse<T>(string xml, RestResponse<T> response)
           where T : new()
        {
            Parse(xml, (RestResponse)response);
            if (response.Error != null)
                return;

            using (TextReader tr = new StringReader(xml))
            {
                XDocument doc = XDocument.Load(tr);
                XElement data = (from c in doc.Root.Descendants().Skip(1)
                                 select c).FirstOrDefault();
                if (data != null)
                {
                    StringBuilder sb = new StringBuilder();
                    using (XmlWriter xw = XmlWriter.Create(sb))
                    {
                        data.WriteTo(xw);
                    }
                    response.Data = SerializationHelper.DeserializeXml<T>(sb.ToString());
                }
            }
        }
    }
}